// Fill out your copyright notice in the Description page of Project Settings.

#pragma once

#include "CoreMinimal.h"
#include "HeaderDataCpp.h"
#include "ItemGridCpp.h"
#include "GameFramework/PlayerState.h"
#include "Engine/DataTable.h"
#include "Kismet/GameplayStatics.h"
#include "PlayerStateBaseCpp.generated.h"


/**
 * 
 */
UCLASS()
class ACTIONGAME_API APlayerStateBaseCpp : public APlayerState
{
	GENERATED_BODY()

protected:
	UPROPERTY(VisibleAnywhere, BlueprintReadOnly)
	int CurrentMapReward;

	UPROPERTY()
	TMap<EItemType, FCollectableItemStruct> ItemsMap;

	UPROPERTY()
	UDataTable* CombinationTable;

	UPROPERTY()
	TMap<EItemType, FCombinationStruct> CombinationMap;

	UPROPERTY()
	float PlayerHP;

	UPROPERTY()
	float BaseDamage;

	UPROPERTY()
	float ProDamage;

	UPROPERTY()
	float Power;

	UPROPERTY(EditAnywhere, BlueprintReadOnly)
	float PowerIncreasingSpeed;

	UPROPERTY(EditAnywhere, BlueprintReadOnly)
	float PowerDecreasingSpeed;
	
public:
	APlayerStateBaseCpp();
public:
	/**
	 * 增加当前关卡的分数，并不改变总共的分数，UI显示的是上一个关卡累计的得分和当前关卡得分之和，当前关卡结束后将当前关卡的分数更新到总共的分数里。
	 */
	inline void AddReword();

	/**
	 * 返回当前关卡的得分。
	 * @return CurrentMapReward 当前关卡的得分。
	 */
	inline int GetReward() const;

	/**
	 * 返回ItemsMap。
	 * @return ItemsMap TMap<EItemType, FCollectableItemStruct>*，返回的ItemsMap。
	 */
	inline TMap<EItemType, FCollectableItemStruct>* GetItemsMap();
	
	/**
	 * 获取指定类型物品的数量。
	 * @param Type EItemType，物品类型。
	 * @return Cnt int，数量。
	 */
	inline int GetItemCntFromItemsMap(const EItemType Type) const;

	/**
	 * 移除ItemsMap中指定类型物品的指定数量。
	 * @param Type EItemType，要移除的类型。
	 * @param NeedRemoveAmount int，需要移除的数量
	 * @return bool 是否还有剩余
	 */
	inline bool RemoveItemFromItemsMap(const EItemType Type, const int NeedRemoveAmount);

	/**
	 * 向ItemsMap里增加指定物品类型的指定数量。
	 * @param Type EItemType，要增加数量的类型
	 * @param NeedAddAmount int，需要增加的数量
	 */
	inline void AddItemToItemsMap(const EItemType Type, const int NeedAddAmount);

	/**
	 * 从表中读取组合
	 */
	void ReadCombinationTableFromFile();

	/**
	 * 从源类型获取可以合成的目标类型即所需源类型的数量。
	 * @param SrcType EItemType，源类型
	 * @param TgtType EItemType，目标类型
	 * @param Amount int，合成目标类型需要的源类型的数量
	 * @return bool，是否具有该组合
	 */
	bool GetCombinationMap(const EItemType& SrcType, EItemType& TgtType, int& Amount) const;

	/**
	 * 由源类型判断该源类型是否具有合成目标类型的能力
	 * @param SrcType EItemType，源类型
	 * @return bool，配置表中是否有从源类型的组合。
	 */
	bool HasCombination(const EItemType& SrcType) const;

	/**
	 * 返回HP
	 * @return HP float，玩家的HP
	 */
	inline float GetPlayerHP() const;

	/**
	 * 增加指定量的HP
	 * @param Up float，增加的血量
	 */
	inline void IncreasePlayerHP(const float Up);

	/**
	 * 减少指定量的HP
	 * @param Down float，减少的血量
	 */
	inline void DecreasePlayerHP(const float Down);

	/**
	 * 设置指定量的HP
	 * @param AbsHP float，覆写HP
	 */
	inline void SetPlayerHP(const float AbsHP);

	/**
	 * 设置基础伤害
	 * @param BaseValue float，基础伤害
	 */
	inline void SetBaseDamage(const float BaseValue);

	/**
	 * 设置高级伤害
	 * @param ProValue float，高级伤害
	 */
	inline void SetProDamage(const float ProValue);

	/**
	 * 从GameMode获取伤害值
	 */
	inline void SetDamage();

	/**
	 * 获取基本伤害
	 * @return BaseDamage float，基本伤害
	 */
	inline float GetBaseDamage() const;

	/**
	 * 获取高级伤害
	 * @return ProDamage float，高级伤害
	 */
	inline float GetProDamage() const;

	/**
	 * 获取力量值
	 * @return Power float，力量值
	 */
	inline float GetPower() const;

	/**
	 * 减少力量值
	 * @param DeltaValue float，力量值的变化量
	 */
	inline void DecreasePower(const float DeltaValue);

	/**
	 * 增加力量值
	 * @param DeltaValue float，力量值的变化量
	 */
	inline void IncreasePower(const float DeltaValue);

	/**
	 * 获取力量值的增加速度
	 * @return PowerIncreasingSpeed float，力量值的恢复速度
	 */
	inline float GetPowerIncreasingSpeed() const;

	/**
	* 获取力量值的减少速度
	* @return PowerDecreasingSpeed float，力量值的减少速度
	*/
	inline float GetPowerDecreasingSpeed() const;

	UFUNCTION()
	void InitItemMapFromGameInstance();
};
